package org.zuel.lkq.service.impl;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.zuel.lkq.constant.AuthConstant;
import org.zuel.lkq.domain.*;
import org.zuel.lkq.mapper.*;
import org.zuel.lkq.service.AuthQueryService;

import java.util.ArrayList;
import java.util.List;

@Service
public class AuthQueryServiceImpl implements AuthQueryService {

    private UserRoleMapper userRoleMapper;

    private RolePermMapper rolePermMapper;

    private UserMapper userMapper;

    private RoleMapper roleMapper;

    private PermMapper permMapper;

    @Autowired
    public AuthQueryServiceImpl(UserRoleMapper userRoleMapper,
                            RolePermMapper rolePermMapper,
                            UserMapper userMapper,
                            RoleMapper roleMapper,
                            PermMapper permMapper) {
        this.userRoleMapper = userRoleMapper;
        this.rolePermMapper = rolePermMapper;
        this.userMapper = userMapper;
        this.roleMapper = roleMapper;
        this.permMapper = permMapper;
    }

    @Override
    public List<User> queryUsername(String username) {
        UserExample example = new UserExample();
        example.createCriteria().andDeletedEqualTo(false).andUsernameEqualTo(username);
        return userMapper.selectByExample(example);
    }

    @Override
    public List<Role> queryRolesByUser(Integer user) {
        if (user == null) {
            return new ArrayList<>();
        }
        // 查询关联关系
        UserRoleExample mapExample = new UserRoleExample();
        mapExample.setDistinct(true);
        UserRoleExample.Criteria mapCriteria = mapExample.createCriteria();
        mapCriteria.andDeletedEqualTo(false);
        mapCriteria.andUserIdEqualTo(user);
        List<UserRole> mapList = userRoleMapper.selectByExample(mapExample);
        if (mapList == null || mapList.size() == 0) {
            return new ArrayList<>();
        }
        // 查询角色
        List<Integer> roleIds = new ArrayList<>();
        mapList.forEach(map -> {
            if (!roleIds.contains(map.getRoleId())) {
                roleIds.add(map.getRoleId());
            }
        });
        RoleExample example = new RoleExample();
        RoleExample.Criteria criteria = example.createCriteria();
        criteria.andDeletedEqualTo(false);
        criteria.andIdIn(roleIds);
        return roleMapper.selectByExample(example);
    }

    @Override
    public List<Perm> queryPermsByUser(Integer user) {
        // 查询角色
        List<Role> roles = queryRolesByUser(user);
        if (roles.size() == 0) {
            return new ArrayList<>();
        }
        // 查询权限
        List<Integer> roleIds = new ArrayList<>();
        roles.forEach(role -> roleIds.add(role.getId()));
        return queryPermsByRoles(roleIds);
    }

    @Override
    public List<Perm> queryMenusByUser(Integer user) {
        // 查询角色
        List<Role> roles = queryRolesByUser(user);
        if (roles.size() == 0) {
            return new ArrayList<>();
        }
        // 查询权限
        List<Integer> roleIds = new ArrayList<>();
        roles.forEach(role -> roleIds.add(role.getId()));
        return queryMenusByRoles(roleIds);
    }

    @Override
    public List<Perm> queryPermsByRoles(List<Integer> roles, Integer menuId) {
        if (roles == null || roles.size() == 0) {
            return new ArrayList<>();
        }
        // 查询关联关系
        RolePermExample mapExample = new RolePermExample();
        mapExample.setDistinct(true);
        RolePermExample.Criteria mapCriteria = mapExample.createCriteria();
        mapCriteria.andDeletedEqualTo(false);
        mapCriteria.andRoleIdIn(roles);
        List<RolePerm> mapList = rolePermMapper.selectByExample(mapExample);
        if (mapList == null || mapList.size() == 0) {
            return new ArrayList<>();
        }
        // 查询权限
        List<Integer> permIds = new ArrayList<>();
        mapList.forEach(map -> {
            if (!permIds.contains(map.getPermId())) {
                permIds.add(map.getPermId());
            }
        });
        PermExample example = new PermExample();
        example.setDistinct(true);
        PermExample.Criteria criteria = example.createCriteria();
        criteria.andDeletedEqualTo(false);
        criteria.andIdIn(permIds);
        if (menuId != null) {
            criteria.andMenuIdEqualTo(menuId);
        }
        return permMapper.selectByExample(example);
    }

    @Override
    public List<Perm> queryPermsByRoles(List<Integer> roles) {
        return queryPermsByRoles(roles, null);
    }

    @Override
    public List<Perm> queryMenusByRoles(List<Integer> roles) {
        return queryPermsByRoles(roles, 0);
    }

    @Override
    public List<Perm> queryPermsByMenu(Integer menuId) {
        PermExample example = new PermExample();
        PermExample.Criteria criteria = example.createCriteria();
        criteria.andDeletedEqualTo(false).andMenuIdEqualTo(menuId);
        criteria.andPermUrlIsNotNull();
        List<Perm> perms = permMapper.selectByExample(example);
        return perms;
    }


    @Override
    public List<Perm> queryAnonPerms() {
        PermExample example = new PermExample();
        example.setDistinct(true);
        PermExample.Criteria criteria = example.createCriteria();
        criteria.andDeletedEqualTo(false);
        criteria.andAnonStatusEqualTo(AuthConstant.PERM_ANNO_STATUS_YES);
        return permMapper.selectByExample(example);
    }
}
